import store from "../../store/index";
import SessionUtil from "../session/session"
import { Url } from "../../utils/textUtils";

export default class PagePromoterUtil
{
    /**
     * 向全局注册页面的分享/推广来源
     * 
     * @param {PagePromoter} promoter 
     */
    static registryPagePromoter(promoter){
        console.debug('向全局注册页面的分享/推广来源', promoter)
        store.global('common.pagePromoter.PagePromoter', promoter)
    }

    /**
     * 获取最后一个推广来源
     * 
     * @returns {PagePromoter} 没有推广来源时返回undefined
     */
    static getLastPromoter(){
        let promoter = store.global('common.pagePromoter.PagePromoter')
        if(!(promoter instanceof PagePromoter)){
            promoter = undefined
        }
        console.debug('获取最新的推广来源', promoter)
        return promoter
    }

    /**
     * 展示分享按钮
     * 
     * @see [微信小程序-转发](https://developers.weixin.qq.com/miniprogram/dev/framework/open-ability/share.html)
     * @param {Boolean} withShareTicket 是否使用带 shareTicket 的转发 true=带有ticket
     * @returns {Promise} 返回Promise的实例，需要使用then和catch方法处理分享操作成功和失败的情况
     */
    static showShareMenu(withShareTicket = true){
        return (new Promise((resolve, reject)=>{
            wx.showShareMenu({
                withShareTicket: withShareTicket,
                success: function(res){
                    resolve(res)
                },
                fail:function(err){
                    reject(err)
                }
            })
        })).then(res=>{
            // console.debug('开启分享按钮成功', res)
            return res
        }).catch(err=>{
            // console.debug('开启分享按钮失败', res)
            throw err
        })
    }
}

/**
 * 页面推广器
 * 
 * @todo 类中表达的东西有些混乱，需要优化。该类表达了两种情景：
 * > 1. 当前应用运行场景中的推广来源信息，其中常用的方法hasSharer()、getSharer()以及各种getter等
 * > 2. 当前页面转发功能的助手类，其中常用的方法setPath()、setQuery()、setShareTitle()、setShareImage()、buildShareInfo()等
 */
export class PagePromoter
{
    _data = {
        /**
         * @property {{}} sharer 分享者信息
         * @property {Number} sharer.salesmanId
         * @property {Number} sharer.salesmanVCardId
         * @property {Number} sharer.agentId
         * @property {Number} sharer.customerId
         * @property {String} sharer.appletCodeScene
         * @property {String} sharer.qrcodeRedirect
         * @property {Number} sharer.qrcodeRedirectTime
         */
        sharer:{},
        path:'',
        query:{},
        title:'',
        imageUrl:''
    }
    /**
     * 分享标记字段映射关系
     * 
     * @private
     */
    _sharerLabelFieldsMaps(){
        return {
            _salesmanId:'salesmanId',
            salesmanId:'salesmanId',
            salesman_id:'salesmanId',
            _sId:'salesmanId',
            _consultantId:'salesmanVCardId',
            consultantId:'salesmanVCardId',
            consultant_id:'salesmanVCardId',
            _salesmanVCardId:'salesmanVCardId',
            _svId:'salesmanVCardId',
            _gId:'salesGroupId',
            _agentId:'agentId',
            _aId:'agentId',
            aId:'agentId',
            _customerId:'customerId',
            _shareCustId:'customerId',
            _cId:'customerId',
            sn:'sn',
            scene:'scene', // 无限数量的小程序码参数都存在该参数中
            _qrcodeRedirect:'qrcodeRedirect',
            q:'qrcodeRedirect', // 外部二维码跳转进来时，表示二维码链接的内容（已经过url编码）
            _qrcodeRedirectTime:'qrcodeRedirectTime',
            scancode_time:'qrcodeRedirectTime', // 外部二维码跳转进来时，表示扫描二维码链接的时间
        }
    }
    get salesmanId(){
        return this._data.sharer.salesmanId
    }
    get salesmanVCardId(){
        return this._data.sharer.salesmanVCardId
    }
    get agentId(){
        return this._data.sharer.agentId
    }
    get customerId(){
        return this._data.sharer.customerId
    }
    get appletCodeScene(){
        return this._data.sharer.appletCodeScene
    }
    get qrcodeRedirect(){
        return this._data.sharer.qrcodeRedirect
    }
    get qrcodeRedirectTime(){
        return this._data.sharer.qrcodeRedirectTime
    }
    /**
     * 获取分享者的信息
     * 
     * @returns {{_salesmanId: Number,_salesmanVCardId: Number,_agentId: Number,_customerId: Number,_appletCodeScene: String,_qrcodeRedirect: String,_qrcodeRedirectTime: Number}}
     */
    getTheSharer(){
        if(!this.hasSharer()){
            return {}
        }
        return this._data.sharer
    }
    /**
     * 带有分享者信息
     * 
     * @returns {Boolean}
     */
    hasSharer(){
        return (typeof this._data.sharer === 'object' && Object.keys(this._data.sharer).length > 0)
    }

    getPath(){
        return this._data.path+''
    }
    /**
     * 设置分享内容打开的页面路径
     * 
     * @param {String} path 打开的页面路径，支持绝对路径和不以`/`开头的路径(如从当前页面的路由信息中获取的值`Page.route`) 
     */
    setPath(path){
        if(typeof path !== 'string') path = ''
        if(path.length > 0 && path[0] !== '/') path = '/'+path
        this._data.path = path
        return this
    }
    /**
     * 获取query信息
     * 
     * @param {Boolean} withSharer true = 返回分享者信息； false = 过滤分享者信息
     */
    getQuery(withSharer = true){
        let query = this._data.query?this._data.query:{}
        if(withSharer){
           Object.assign(query, this._data.sharer?this._data.sharer:{}) 
        }
        return query
    }
    /**
     * 设置分享的query参数
     * 
     * @param {{}} query 分享时使用的参数(不含分享者信息)
     */
    setQuery(query){
        this._data.query = query
        return this
    }
    /**
     *
     * @param {String} path 页面路径
     * @param {{}} query 页面onLoad时回调的参数或者分享时使用的参数
     */
    constructor(path, query){
        let _query={},_sharer={}
        if(typeof query === 'object' && Object.keys(query).length > 0){
            let sharerKeysMap = this._sharerLabelFieldsMaps()
            // query参数解析函数，根据映射表筛选出带有推广来源信息的参数
            let convertQuery = (q)=>{
                let queryKeys = Object.keys(q)
                queryKeys.forEach(key => {
                    if(typeof sharerKeysMap[key] === 'string'){
                        _sharer[sharerKeysMap[key]] = q[key]
                    }else{
                        _query[key] = q[key]
                    }
                })
            }
            // 筛选页面加载的option中的参数
            convertQuery(query)
            if(query.scene){ // 筛选option.scene中的参数，option.scene中的参数会覆盖option中的同名参数
                convertQuery(Url.parseQuery(query.scene))
            }
        }
        if(path) this.setPath(path)
        this._data.query = _query
        this._data.sharer = _sharer
    }
    /**
     * 设置分享的标题
     * 
     * @param {String} title 
     */
    setShareTitle(title){
        this._data.title = title
        return this
    }
    getShareTitle(){
        return this._data.title+''
    }
    /**
     * 设置自定义图片
     * 
     * + 支持PNG及JPG
     * + 显示图片长宽比是 5:4
     * 
     * @param {String} url 图片的地址，为空时表示使用应用截图
     */
    setShareImage(url){
        this._data.imageUrl = url
        return this
    }
    /**
     * @returns {String}
     */
    getShareImage(){
        return this._data.imageUrl + ''
    }
    /**
     * 构造分享的正文
     * 
     * 返回的结果可以直接作为事件处理函数`onShareAppMessage`的返回值返回
     */
    buildShareInfo(){
      let config = {
          path:this._getSharePath()
      }
      if(this.getShareTitle()){
          config.title = this.getShareTitle()
      }
      if(this.getShareImage()){
          config.imageUrl = this.getShareImage()
      }
      return config
    }
    /**
     * 获取用于分享的页面路径
     * 
     * @private
     * 包含页面路径、业务参数、分享者参数
     */
    _getSharePath(){
        if(!this.hasSharer()){
            this._autoSetSharer()
        }
        let query = this.getQuery(),params = []
        Object.keys(query).forEach(key=>{
            if(typeof query[key] === 'undefined'){
                query[key] = ''
            }
            params.push(key+'='+query[key])
        })
        let queryString = params.join('&')
        return this.getPath()+'?'+queryString
    }
    /**
     * 自动获取并设置分享人信息
     * 
     * @private
     * @returns {{}} sharer
     */
    _autoSetSharer(){
        let session = SessionUtil.getInstanceSync()
        let user = session.getTheSessionUserSync(),sellingServer = session.getTheSellingServerSync()
        this._data.sharer = {
            _salesmanId: sellingServer.salesmanId,
            _customerId: user.userId
        }
    }

}